/* Orbas:
 *     A open source CORBA Specification implementation from Huihoo.
 *
 * Copyright 2002-2003 Huihoo.org, Inc. All Right Reserved.
 *
 * This software is licensed under LGPL license.
 * See terms of license at gnu.org.
 *
 * For more information, visit:
 *
 * http://www.huihoo.org/orbas
 */

package org.huihoo.orbas.orb.protocols.iiop;

/**
 * <p>Description: </p>
 * IIOP profiles creator.
 * <p>Copyright (c) 2002,2003</p>
 * <p>Company: <a href="http://www.huihoo.org/">huihoo.org</a></p>
 * @author <a href="http://www.huihoo.org/~mep">mep(mep@huihoo.com)</a>
 * @see <a href="http://www.huihoo.org/orbas">http://www.huihoo.org/orbas</a>
 * @version 1.0
 */

import org.huihoo.orbas.orb.cdr.CDROutputStream;
import org.huihoo.orbas.orb.protocols.Channel;
import org.huihoo.orbas.orb.protocols.ProfileCreator;

//import org.omg.IIOP.*;

public class IiopProfileCreator extends ProfileCreator {

	IiopChannel ch;
	short port;

	public IiopProfileCreator(CDROutputStream out) {
		super(out);
		port = Iiop.TCP_PORT;
	}

	public IiopProfileCreator() {
		port = Iiop.TCP_PORT;
	}

	public Channel createChannel() {
		if (ch == null) {

			ch = new IiopChannel();

			try {
				ch.setServerPort(port);
			} catch (java.io.IOException ex) {
				// if failed,open a random socket
				try {
					ch.setServerPort(0);
				} catch (java.io.IOException e) {
					System.out.println("Cannot create server socket.");
					e.printStackTrace();
				}
			}
		}
		port = (short) ch.getServerPort();

		return ch;
	}

	public org.omg.IOP.TaggedProfile[] createProfiles(byte[] objectKey,
			int version) {

		if (ch == null) {
			createChannel();
		}

		org.omg.IOP.TaggedProfile[] profiles = new org.omg.IOP.TaggedProfile[1];
		org.omg.IOP.TaggedProfile profile;
		java.net.InetAddress addr = null;
		try {
			addr = java.net.InetAddress.getLocalHost();
		} catch (java.net.UnknownHostException e) {
			System.out.println("Error:Can not get local host address");
			e.printStackTrace();
			return null;
		}

		switch (version) {
		case 10:
			org.omg.IIOP.ProfileBody_1_0 profile10 = new org.omg.IIOP.ProfileBody_1_0();

			profile10.iiop_version = new org.omg.IIOP.Version();
			profile10.iiop_version.major = 1;
			profile10.iiop_version.minor = 0;
			profile10.host = addr.getHostAddress();
			profile10.port = port;
			profile10.object_key = objectKey;

			CDROutputStream out0 = new CDROutputStream(null);

			// byte flag cannot omitted here
			out0.write_boolean(false);
			org.omg.IIOP.ProfileBody_1_0Helper.write(out0, profile10);

			byte[] data0 = new byte[out0.getLength()];
			System.arraycopy(out0.getBuffer(), 0, data0, 0, out0.getLength());
			profile = new org.omg.IOP.TaggedProfile(
					org.omg.IOP.TAG_INTERNET_IOP.value, data0);
			profiles[0] = profile;

			break;

		case 11:

			org.omg.IIOP.ProfileBody_1_1 profile11 = new org.omg.IIOP.ProfileBody_1_1();

			profile11.iiop_version = new org.omg.IIOP.Version();
			profile11.iiop_version.major = 1;
			profile11.iiop_version.minor = 1;
			profile11.host = addr.getHostAddress();
			profile11.port = port;
			profile11.object_key = objectKey;
			profile11.components = new org.omg.IOP.TaggedComponent[0];

			CDROutputStream out1 = new CDROutputStream(null);

			// byte flag cannot omitted here
			out1.write_boolean(false);
			org.omg.IIOP.ProfileBody_1_1Helper.write(out1, profile11);

			byte[] data1 = new byte[out1.getLength()];
			System.arraycopy(out1.getBuffer(), 0, data1, 0, out1.getLength());
			profile = new org.omg.IOP.TaggedProfile(
					org.omg.IOP.TAG_INTERNET_IOP.value, data1);

			profiles[0] = profile;

			break;

		case 12:

			org.omg.IIOP.ProfileBody_1_1 profile12 = new org.omg.IIOP.ProfileBody_1_1();

			profile12.iiop_version = new org.omg.IIOP.Version();
			profile12.iiop_version.major = 1;
			profile12.iiop_version.minor = 2;
			profile12.host = addr.getHostAddress();
			profile12.port = port;
			profile12.object_key = objectKey;
			profile12.components = new org.omg.IOP.TaggedComponent[0];

			CDROutputStream out2 = new CDROutputStream(null);

			// byte flag cannot omitted here
			out2.write_boolean(false);
			org.omg.IIOP.ProfileBody_1_1Helper.write(out2, profile12);

			byte[] data2 = new byte[out2.getLength()];
			System.arraycopy(out2.getBuffer(), 0, data2, 0, out2.getLength());
			profile = new org.omg.IOP.TaggedProfile(
					org.omg.IOP.TAG_INTERNET_IOP.value, data2);

			profiles[0] = profile;

			break;

		default:
			// error!

		}

		return profiles;
	}

}